package com.xqboss.apps.controller.consumer;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.google.common.collect.Lists;
import com.xqboss.apps.domain.consumer.ConsumerTeam;
import com.xqboss.apps.domain.consumer.ConsumerTeamApply;
import com.xqboss.apps.domain.consumer.ConsumerTeamMember;
import com.xqboss.apps.domain.consumer.ConsumerTeamMsgRecord;
import com.xqboss.apps.dto.PageDto;
import com.xqboss.apps.dto.consumer.*;
import com.xqboss.apps.service.consumer.ConsumerTeamApplyService;
import com.xqboss.apps.service.consumer.ConsumerTeamMemberService;
import com.xqboss.apps.service.consumer.ConsumerTeamMsgRecordService;
import com.xqboss.apps.service.consumer.ConsumerTeamService;
import com.xqboss.apps.vo.consumer.*;
import com.xqboss.common.annotation.Log;
import com.xqboss.common.annotation.RepeatSubmit;
import com.xqboss.common.core.controller.BaseController;
import com.xqboss.common.core.domain.AjaxResult;
import com.xqboss.common.core.domain.R;
import com.xqboss.common.enums.BusinessType;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import java.util.Optional;

/**
 * 队伍Controller
 *
 * @author xqboss
 * @date 2023-08-15
 */
@Api(tags = {"队伍管理"})
@RestController
@RequestMapping("/apps/consumer/team")
public class ConsumerTeamController extends BaseController {
    @Autowired
    private ConsumerTeamService consumerTeamService;

    @Autowired
    private ConsumerTeamApplyService consumerTeamApplyService;

    @Autowired
    private ConsumerTeamMsgRecordService consumerTeamMsgRecordService;

    @Autowired
    private ConsumerTeamMemberService consumerTeamMemberService;

    @ApiOperation("我的队伍排行信息")
    @PostMapping("/my-team-rank")
    public R<ConsumerTeamRankVo> myTeamInfo(@RequestBody Object dto) {
        ConsumerTeamRankVo myTeamRank = consumerTeamService.getMyTeamRank(getUserId());
        return R.ok(myTeamRank);
    }

    @ApiOperation("好友队伍排行榜列表v23.8.3.1")
    @PostMapping("/top-list")
    public R<List<ConsumerTeamVo>> list(@RequestBody ConsumerTeamDto dto) {
        dto.setUserId(getUserId());
        return consumerTeamService.topList(dto);
    }

    @ApiOperation("队伍总排行榜")
    @PostMapping("/total_top-list")
    public R<List<ConsumerTeamTotalTopVo>> totalTopList(@RequestBody ConsumerTeamTotalTopDto dto) {
        LambdaQueryWrapper<ConsumerTeam> wp = new LambdaQueryWrapper<>();
        if (StrUtil.isNotBlank(dto.getSearch())) {
            wp.like(ConsumerTeam::getName, dto.getSearch()).or();
            wp.eq(ConsumerTeam::getId, dto.getSearch());
        }
        wp.orderByDesc(ConsumerTeam::getTodayPunchCount);
        wp.orderByAsc(ConsumerTeam::getId);
        if (dto.getPageNum() > 1) {
            return R.ok(CollUtil.newArrayList());
        }
        dto.setPageNum(1);
        dto.setPageSize(30);
        dto.startPage();
        List<ConsumerTeam> list = consumerTeamService.list(wp);
        List<ConsumerTeamTotalTopVo> voList = BeanUtil.copyToList(list, ConsumerTeamTotalTopVo.class);
        //设置当前登录用户是否在对应队伍中
        ConsumerTeamMember teamMember = consumerTeamMemberService.lambdaQuery().select(ConsumerTeamMember::getTeamId).eq(ConsumerTeamMember::getUserId, getUserId()).one();
        Integer teamId = Optional.ofNullable(teamMember).orElse(new ConsumerTeamMember()).getTeamId();
        Optional.ofNullable(teamId).ifPresent(tId->{
            Optional<ConsumerTeamTotalTopVo> opt = voList.stream().filter(v -> Objects.equals(v.getId(), teamId)).findFirst();
            ConsumerTeamTotalTopVo vo = opt.orElse(null);
            Integer index = opt.map(voList::indexOf).orElse(null);
            Optional.ofNullable(vo).ifPresent(v-> v.setIsExistTeam(Boolean.TRUE));
            Optional.ofNullable(index).ifPresent(v-> voList.set(index,vo));
        });

        return R.ok(voList, list);
    }

    @ApiOperation("队伍详情")
    @GetMapping(value = "info/{teamId}")
    public R<ConsumerTeamInfoVo> getInfo(@PathVariable("teamId") @ApiParam(value = "队伍id", required = true) Integer teamId) {
        Long userId = getUserId();
        ConsumerTeamInfoVo vo = consumerTeamService.selectConsumerTeamById(teamId, userId);
        return R.ok(vo);
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("退出队伍")
    @GetMapping(value = "quit/{teamId}")
    public R quit(@PathVariable("teamId") @ApiParam(value = "队伍id", required = true) Integer teamId) {
        Long userId = getUserId();
        return consumerTeamService.quit(teamId, userId);
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("加入队伍v23.8.3.1")
    @PostMapping(value = "join")
    public R joinTeam(@Validated @RequestBody ConsumerTeamMsgRecordDto dto) {
        dto.setUserId(getUserId());
        return consumerTeamService.joinTeam(dto);
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("邀请好友加入队伍")
    @PostMapping(value = "inviteJoin")
    public R inviteJoin(@Validated @RequestBody ConsumerTeamMsgRecordDto dto) {
        dto.setUserId(getUserId());
        return consumerTeamService.inviteJoinTeam(dto);
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("创建队伍v23.8.3.1")
    @Log(title = "创建队伍", businessType = BusinessType.INSERT)
    @PostMapping("add")
    public AjaxResult add(@RequestBody ConsumerTeamDto consumerTeamDTO) {
        consumerTeamDTO.setCreateUserId(getUserId());
        if (StrUtil.isBlank(consumerTeamDTO.getName())) {
            consumerTeamDTO.setName(getUsername() + "的队伍");
        }
        return toAjax(consumerTeamService.insertConsumerTeam(consumerTeamDTO));
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("编辑队伍")
    @Log(title = "编辑队伍", businessType = BusinessType.UPDATE)
    @PutMapping("edit")
    public R edit(@RequestBody ConsumerTeamDto consumerTeamDTO) {
        return consumerTeamService.updateConsumerTeam(consumerTeamDTO);
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("删除成员")
    @Log(title = "删除成员", businessType = BusinessType.DELETE)
    @DeleteMapping("delete")
    public R remove(@Validated @RequestBody ConsumerTeamDelDto dto) {
        return consumerTeamService.deleteMemberByUserIds(dto);
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("编辑队伍申请记录")
    @Log(title = "编辑队伍申请记录", businessType = BusinessType.UPDATE)
    @PutMapping("/apply-edit")
    public R applyEdit(@RequestBody ConsumerApplyDto dto) {
        dto.setUserId(getUserId());
        return consumerTeamApplyService.updateConsumerApply(dto);
    }

    @ApiOperation("队伍申请列表记录")
    @PostMapping("/apply-list")
    public R<List<ConsumerTeamApplyVo>> applyList(@RequestBody ConsumerApplyDto dto) {
        dto.startPage();
        List<ConsumerTeamApplyVo> list = Lists.newArrayList();
        ConsumerTeamApply wrapper = new ConsumerTeamApply();
        switch (dto.getApplyEnum()) {
            case FRIEND_APPLY:
                wrapper.setHandlerUserId(getUserId());
                wrapper.setType(1);
                list = consumerTeamApplyService.selectByDto(wrapper);
                break;
            case MY_APPLY:
                wrapper.setUserId(getUserId());
                wrapper.setType(1);
                list = consumerTeamApplyService.getMyApply(wrapper);
                break;
            case INVITE_MINE:
                wrapper.setHandlerUserId(getUserId());
                wrapper.setType(2);
                list = consumerTeamApplyService.selectByDto(wrapper);
                break;
        }
        return R.ok(list);
    }

    @ApiOperation("队伍消息记录")
    @PostMapping(value = "/msg-list")
    public R<List<ConsumerTeamMsgRecordVo>> msgList(@Validated @RequestBody ConsumerTeamMsgRecordDto params) {
        params.setUserId(getUserId());

        LambdaQueryWrapper<ConsumerTeamMsgRecord> wq = new LambdaQueryWrapper<>();
        wq.eq(ConsumerTeamMsgRecord::getTeamId, params.getTeamId());
        wq.orderByDesc(ConsumerTeamMsgRecord::getId);
        params.startPage();
        List<ConsumerTeamMsgRecord> msgRecords = consumerTeamMsgRecordService.list(wq);
        if (CollUtil.isEmpty(msgRecords)) {
            return R.ok(new ArrayList<>());
        }
        List<ConsumerTeamMsgRecordVo> vo = consumerTeamMsgRecordService.msgList(msgRecords);
        return R.ok(vo, msgRecords);
    }

    @ApiOperation("飘屏弹幕-队伍消息记录")
    @PostMapping(value = "/barrage-msg-list")
    public R<List<ConsumerTeamMsgRecordVo>> barrageMsgList(@RequestBody PageDto dto) {
        Long userId = getUserId();
        LambdaQueryWrapper<ConsumerTeamMember> wqTeam = new LambdaQueryWrapper<>();
        wqTeam.eq(ConsumerTeamMember::getUserId, userId);
        ConsumerTeamMember teamMember = consumerTeamMemberService.getOne(wqTeam);
        if (Objects.isNull(teamMember)) {
            return R.ok();
        }

        LambdaQueryWrapper<ConsumerTeamMsgRecord> wq = new LambdaQueryWrapper<>();
        wq.eq(ConsumerTeamMsgRecord::getTeamId, teamMember.getTeamId());
        wq.gt(ConsumerTeamMsgRecord::getId, teamMember.getTeamMsgId() == null ? 1 : teamMember.getTeamMsgId());
//        wq.orderByDesc(ConsumerTeamMsgRecord::getId);
        dto.startPage();
        List<ConsumerTeamMsgRecord> msgRecords = consumerTeamMsgRecordService.list(wq);
        if (CollUtil.isEmpty(msgRecords)) {
            return R.ok();
        }
        List<ConsumerTeamMsgRecordVo> vo = consumerTeamMsgRecordService.msgList(msgRecords);
        //更新队伍成员已读记录的位置id
        consumerTeamMemberService.update(new LambdaUpdateWrapper<ConsumerTeamMember>()
                .set(ConsumerTeamMember::getTeamMsgId, vo.stream().findFirst().get().getId())
                .eq(ConsumerTeamMember::getId, teamMember.getId()));
        return R.ok(vo, msgRecords);
    }

    @RepeatSubmit(interval = 1000, justUrl = true)
    @ApiOperation("提醒打卡/点赞/送爱心")
    @PostMapping(value = "/punch-upvote-love")
    public R punchUpvoteLove(@Validated @RequestBody ConsumerTeamMsgRecordDto params) {
        params.setUserId(getUserId());
        return consumerTeamService.punchUpvoteLove(params);
    }
}
